﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Drawing2D;

namespace Maydew.Windows.Forms.Controls.FlexiCell
{
    /// <summary>
    /// 为单元格提供图像编辑器。
    /// </summary>
    public class PictureCellEditor : CellEditor
    {
        #region " 私有方法 "
        /// <summary>
        /// 图像编辑控件。
        /// </summary>
        private PictureBox _editor;
        private Rectangle _addButton;
        #endregion

        #region " 构造函数 "
        /// <summary>
        /// 初始化 PictureCellEditor 类的新实例。
        /// </summary>
        public PictureCellEditor()
        {
            _editor = new PictureBox();
            _editor.BackColor = Color.White;
            _editor.SizeMode = PictureBoxSizeMode.Zoom;
            _editor.Paint += new PaintEventHandler(_editor_Paint);
            _editor.MouseClick += new MouseEventHandler(_editor_MouseClick);
            _editor.BorderStyle = BorderStyle.None;
            Editor = _editor;
        }
        
        #endregion

        #region " PictureBox 处理 "
        private void _editor_MouseClick(object sender, MouseEventArgs e)
        {
            if (_addButton.Contains(e.Location))
            {
                OpenFileDialog form = new OpenFileDialog();
                if (form.ShowDialog() == DialogResult.Cancel) return;
                _editor.Image = new Bitmap(form.FileName);
            }
        }

        private void _editor_Paint(object sender, PaintEventArgs e)
        {
            int width = 20;
            int height = 20;
            int x = (_editor.Width - width) / 2;
            int y = (_editor.Height - height) / 2;
            _addButton = new Rectangle(x, y, width, height);
            GraphicsPath path = new GraphicsPath();
            int arc = 6;
            path.AddArc(x, y, arc, arc, 180, 90);
            path.AddArc(_addButton.Right - arc, y, arc, arc, 270, 90);
            path.AddArc(_addButton.Right - arc, _addButton.Bottom - arc, arc, arc, 0, 90);
            path.AddArc(x, _addButton.Bottom - arc, arc, arc, 90, 90);
            path.CloseAllFigures();
            e.Graphics.SmoothingMode = SmoothingMode.HighQuality;
            using (Brush brush = new SolidBrush(Color.FromArgb(100, Color.Silver)))
            {
                e.Graphics.FillPath(brush, path);
            }
            using (Pen pen = new Pen(Color.FromArgb(200, Color.WhiteSmoke)))
            {
                e.Graphics.DrawPath(pen, path);
            }
            path.Dispose();
            path = new GraphicsPath();
            List<Point> list = new List<Point>();
            list.Add(new Point(x + width/2 - arc/2, y + arc / 2));
            list.Add(new Point(x + width / 2 + arc / 2, y + arc / 2));
            list.Add(new Point(x + width / 2 + arc / 2, y + height / 2 - arc / 2));
            list.Add(new Point(x + width - arc / 2, y + height / 2 - arc / 2));
            list.Add(new Point(x + width - arc / 2, y + height / 2 + arc / 2));
            list.Add(new Point(x + width / 2 + arc / 2, y + height / 2 + arc / 2));
            list.Add(new Point(x + width / 2 + arc / 2, y + height - arc / 2));
            list.Add(new Point(x + width / 2 - arc / 2, y + height - arc / 2));
            list.Add(new Point(x + width / 2 - arc / 2, y + height / 2 + arc / 2));
            list.Add(new Point(x + arc / 2, y + height / 2 + arc / 2));
            list.Add(new Point(x + arc / 2, y + height / 2 - arc / 2));
            list.Add(new Point(x + width / 2 - arc / 2, y + height / 2 - arc / 2));
            path.AddLines(list.ToArray());
            using (Brush brush = new SolidBrush(Color.FromArgb(155, Color.White)))
            {
                e.Graphics.FillPath(brush, path);
            }
            path.Dispose();
            path = null;
        }
        #endregion

        #region " 友元方法 "
        /// <summary>
        /// 设置编辑器值时。
        /// </summary>
        protected override void OnSetEditorValue()
        {
            if (Owner.Value is Image)
            {
                _editor.Image = Owner.Value as Image;
            }
        }
        /// <summary>
        /// 获取编辑器值时。
        /// </summary>
        protected override void OnGetEditorValue()
        {
            Owner.Value = _editor.Image;
        }
        /// <summary>
        /// 显示编辑器时。
        /// </summary>
        protected override void OnShowEditor()
        {
            base.OnShowEditor();
        }
        #endregion

        #region " 绘制方法 "
        /// <summary>
        /// 绘制编辑器。
        /// </summary>
        /// <param name="g">绘图参数。</param>
        public override void Painting(Graphics g)
        {
            if (_editor.Image == null) return;
            Image bitmap = _editor.Image;
            int w = Owner.Width;
            int h = bitmap.Height * w / bitmap.Width;
            if (w > Owner.Width || h > Owner.Height)
            {
                h = Owner.Height;
                w = bitmap.Width * h / bitmap.Height;
            }
            int x = Owner.Left + (Owner.Width - w) / 2;
            int y = Owner.Top + (Owner.Height - h) / 2;
            Rectangle srcRect = new Rectangle(0, 0, bitmap.Width, bitmap.Height);
            Rectangle destRect = new Rectangle(x+1, y+1, w-1, h-1);
            g.DrawImage(bitmap, destRect, srcRect, GraphicsUnit.Pixel);
        }
        #endregion

        public override object Clone()
        {
            return new PictureCellEditor();
        }
    }
}
